package com.hsnn.medstgmini.base.dict.dao.impl;

import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.UUID;

import javax.annotation.Resource;

import org.apache.commons.lang3.StringUtils;
import org.hibernate.Criteria;
import org.hibernate.Query;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.criterion.Restrictions;
import org.hibernate.transform.Transformers;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;

import com.hsnn.medstgmini.base.dict.dao.DicPharDao;
import com.hsnn.medstgmini.base.dict.model.DicPhar;
import com.hsnn.medstgmini.dao.impl.HibernateSqlUtilImpl;
import com.hsnn.medstgmini.util.Pagination;
import com.hsnn.medstgmini.util.ParseDate;

/**
 * @category 药理分类字典
 * @author CCL
 */
@Repository
public class DicPharDaoImpl implements DicPharDao {

	@Resource(name = "sessionFactory")
	private SessionFactory sessionFactory;
	
	@Autowired
	private HibernateSqlUtilImpl dao;

	/**
	 * @category 根据id查询药理分类
	 * @param id
	 * @return
	 */
	public DicPhar getDicPharById(String id) {
		if (id != null && !"".equals(id)) {
			Session session = sessionFactory.getCurrentSession();
			Criteria criteria = session.createCriteria(DicPhar.class);
			criteria.add(Restrictions.eq("pharId", id));
			return (DicPhar) criteria.uniqueResult();
		}
		return null;
	}

	/**
	 * @category 查询药理分类维护记录列表
	 * @param result
	 * @param dicPhar
	 * @return
	 */
	@Override
	public Pagination getDicPharLogList(Pagination page) {
		String startTime = page.getConditions().get("startTime");
		String endTime = page.getConditions().get("endTime");
		String pharId = page.getConditions().get("pharId");
		StringBuffer sql = new StringBuffer()
		   .append("select a.detail,a.log_id logId,a.phar_code pharCode,a.phar_Name pharName,a.status status,DATE_FORMAT(a.upd_datetime,'%Y-%m-%d %H:%i:%S') updDatetime,	 ")
		   .append("b.name updUser from dic_phar_log a left join sys_user b on b.id = a.upd_user where a.phar_id = :pharId  ");
		Map<String,String> params = new HashMap<String,String>();
		params.put("pharId", pharId);
		if(StringUtils.isNotBlank(startTime)){
			sql.append(" and DATE_FORMAT(a.upd_datetime,'%Y-%m-%d %H:%i:%S') >= :startTime  ");
			params.put("startTime", startTime+" 00:00:00");
		}
		if(StringUtils.isNotBlank(startTime)){
			sql.append(" and DATE_FORMAT(a.upd_datetime,'%Y-%m-%d %H:%i:%S') <= :endTime  ");
			params.put("endTime", endTime+" 23:59:59");
		}
		sql.append(" order by a.upd_datetime desc ");
		return dao.getSqlPageMapList(sql.toString(), params, page);
	}

	
	@Override
	public Pagination getDicPharList(Pagination page){
		//String fatherId = page.getConditions().get("fatherId");
		String pharId = page.getConditions().get("pharId");
		String leve = page.getConditions().get("leve");
		String pharCode = page.getConditions().get("pharCode");
		String pharName = page.getConditions().get("pharName");
		String status = page.getConditions().get("status");
		Map<String,Object> params = new HashMap<String,Object>();
		StringBuffer sql = new StringBuffer()
		   .append("	SELECT  c.hierarchy hierarchy,c.phar_id,c.phar_code,c.phar_name,c.status,  ")
		   .append("	LENGTH(c.hierarchy) - LENGTH(REPLACE(c.hierarchy, '.', '')) leve, c.father_id, ")
		   .append("	CASE WHEN (  ")
		   .append("    SELECT a.phar_name FROM ")
		   .append("	(SELECT phar_name,phar_id FROM dic_phar where 1=1 ")
		   .append("	)a LEFT JOIN   ")
		   .append("    (SELECT phar_name,phar_id,father_id FROM dic_phar where 1=1 ")
		   .append("    )b ON b.father_id = a.phar_id ")
		   .append("	WHERE b.phar_id IS NULL AND a.phar_id = c.phar_id ")
		   .append("	) IS NULL THEN 'false' ELSE 'true' END leaf,'true' ")
		   .append("	FROM dic_phar c  where 1=1 ");
		if(StringUtils.isNotBlank(pharCode)){
			sql.append(" and c.phar_code = :pharCode ");
			params.put("pharCode", pharCode);
		}
		if(StringUtils.isNotBlank(pharName)){
			sql.append(" and c.phar_name like :pharName ");
			params.put("pharName", "%"+pharName+"%");
		}
		if(StringUtils.isNotBlank(status)){
			sql.append(" and c.status = :status ");
			params.put("status", status);
		}

		if(StringUtils.isNotBlank(pharId)){
			sql.append(" and c.father_id = :pharId ");
			params.put("pharId", pharId);
		}
		if(StringUtils.isNotBlank(leve)){
			leve = (Integer.parseInt(leve)+1)+"";
			if("0".equals(leve)){
				if(StringUtils.isBlank(pharName)&&StringUtils.isBlank(pharCode)&&StringUtils.isBlank(status)){
					sql.append("  AND (LENGTH(c.hierarchy) - LENGTH(REPLACE(c.hierarchy,'.',''))) = :leve ");
					params.put("leve", leve);
				}
			}
		}
		sql.append(" order by c.hierarchy ");
		page.setRows(dao.getSqlList(sql.toString(), params));
		return page;
	}
	
	/**
	 * @category 获取企业资质 类型日志详情
	 * @date 2015年7月13日
	 * @return page
	 */
	@SuppressWarnings("unchecked")
	@Override
	public List<Map<String,Object>> getPharLogDetail(String id){
		Map<String,String> params = new HashMap<String, String>();
		StringBuffer sql = new StringBuffer();
		sql.append("select t.phar_code pharCode,t.phar_name pharName,t.status status,DATE_FORMAT(t.upd_datetime,'%Y-%m-%d %H:%i:%S') updDatetime,p.name updUser  ")
		   .append(" from dic_phar_log t left join sys_user p on p.id = t.upd_user ")
		   .append("  where t.phar_id = (select b.phar_id from dic_phar_log b where b.log_id = :id)  ")
		   .append(" and t.upd_datetime <= (select a.upd_datetime from  dic_phar_log a where a.log_id = :id) ")
		   .append(" order by t.upd_datetime desc limit 2 ");
		params.put("id", id);
		return (List<Map<String, Object>>) dao.getSqlMapList(sql.toString(), params);
	}
	
	/**
	 * @category 启用|停用
	 * @date 2015年7月13日
	 * @return page
	 */
	@SuppressWarnings("unchecked")
	@Override
	public Pagination changeStatus(Pagination page){
		String status = page.getConditions().get("status");
		String updUser = page.getConditions().get("updUser");
		List<String> hierarchyList = (List<String>) page.getForm();
		String hierarchys = page.getConditions().get("hierarchys");
		Session session = sessionFactory.getCurrentSession();
		if("0".equals(status)){
			StringBuffer sb = new StringBuffer()
			.append("select hierarchy from dic_phar where hierarchy REGEXP :hierarchys and status <> 0 ");
			Query query1 = session.createSQLQuery(sb.toString());
			query1.setString("hierarchys", hierarchys);
			List<Object> data = query1.list();
			List<String> list = new ArrayList<String>();
			for(int i = 0;i<data.size();i++){
				list.add(data.get(i).toString());
			}
			page.setForm(list);
		}
		
		StringBuffer sql = new StringBuffer()
		.append("update dic_phar t set t.status = :status,t.upd_datetime = :updDatetime,t.upd_user = :updUser where t.hierarchy  ")
		.append("1".equals(status)?"in (:hierarchyList)":"REGEXP :hierarchys and t.status <> 0 ");
		Query query = session.createSQLQuery(sql.toString());
		query.setString("updDatetime", ParseDate.parseFullFormat(new Date()));
		query.setString("status", status);
		query.setString("updUser", updUser);
		if("1".equals(status)){
			query.setParameterList("hierarchyList", hierarchyList);
		}else{
			query.setString("hierarchys", hierarchys);
		}
		query.executeUpdate();
		session.flush();
		writeLog(page);
		return page;
	}
	
	/**
	 * @category 写日志
	 * @date 2015年7月13日
	 */
	@SuppressWarnings("unchecked")
	public void writeLog(Pagination page){
		String status = page.getConditions().get("status");
		List<String> hierarchyList = (List<String>) page.getForm();
		Session session = sessionFactory.getCurrentSession();
		StringBuffer sql = new StringBuffer()
		.append(" insert into dic_phar_log select uuid(),t.*,:detail from dic_phar t where t.hierarchy  in (:hierarchyList) ");
		Query query = session.createSQLQuery(sql.toString());
		query.setParameterList("hierarchyList", hierarchyList);
		query.setString("detail", "1".equals(status)?"状态由停用变为启用":"状态由启用变为停用");
		query.executeUpdate();
		session.flush();
	}
	
	/**
	 * @category 根据一条id写一条日志
	 * @date 2015年7月13日
	 */
	@SuppressWarnings("unchecked")
	public void writeLog(String pharId){
		Session session = sessionFactory.getCurrentSession();
		StringBuffer sb = new StringBuffer()
		   .append("select phar_code pharCode,phar_name pharName,status from dic_phar where phar_id = :pharId ")
		   .append(" UNION  all ")
		   .append("select t.* from (select phar_code pharCode,phar_name pharName,status from dic_phar_log where phar_id = :pharId order by upd_datetime desc limit 1) t ");
		Query query1 = session.createSQLQuery(sb.toString());
		query1.setString("pharId", pharId);
		query1.setResultTransformer(Transformers.ALIAS_TO_ENTITY_MAP);
		List<Map<String,Object>> list = query1.list();
		StringBuffer detail = new StringBuffer();
		if(list.size()==1){
			detail.append("新增数据<br/>编码：")
			      .append(list.get(0).get("pharCode").toString())
			      .append("<br/>名称：")
			      .append(list.get(0).get("pharName").toString());
		}else{
			if(!list.get(0).get("pharCode").toString().equals(list.get(1).get("pharCode").toString())){
				detail.append("编码由")
				      .append(list.get(1).get("pharCode").toString())
				      .append("变为")
				      .append(list.get(0).get("pharCode").toString());
			}
			if(!list.get(0).get("pharName").toString().equals(list.get(1).get("pharName").toString())){
				detail.append("<br/>名称由")
				      .append(list.get(1).get("pharName").toString())
				      .append("变为")
				      .append(list.get(0).get("pharName").toString());
			}
			if(!list.get(0).get("status").toString().equals(list.get(1).get("status").toString())){
				detail.append("<br/>状态由")
				      .append("1".equals(list.get(1).get("status").toString())?"启用":"停用")
				      .append("变为")
				      .append("1".equals(list.get(0).get("status").toString())?"启用":"停用");
			}
			if(detail.indexOf("<br/>")==0){
				detail.delete(0, 5);
			}
		}
		
		StringBuffer sql = new StringBuffer()
		.append(" insert into dic_phar_log select uuid(),t.*,:detail from dic_phar t where t.phar_id = :pharId  ");
		Query query2 = session.createSQLQuery(sql.toString());
		query2.setString("pharId", pharId);
		query2.setString("detail", detail.toString());
		query2.executeUpdate();
		session.flush();
	}
	
	/**
	 * 比对code或者name是否有重复
	 * @param column
	 * @param value
	 * @param pharId
	 * @return
	 */
	@SuppressWarnings("unchecked")
	@Override
	public List<Object> checkRepeat(String column, String value,String pharId) {
		Session session = sessionFactory.getCurrentSession();
		StringBuffer sql = new StringBuffer();
		sql.append("select * from dic_phar where ")
		   .append(column)
		   .append(" = ? and  phar_id <> ? ");
		Query query = session.createSQLQuery(sql.toString());
		query.setParameter(0, value);
		query.setParameter(1,pharId);
		return query.list();
	}
	
	/**
	 * @category 编辑保存
	 * @date 2015年7月13日
	 */
	@Override
	public void editSave(Pagination page){
		Session session = sessionFactory.getCurrentSession();
		String pharCode = page.getConditions().get("pharCode");
		String pharName = page.getConditions().get("pharName");
		String pharId = page.getConditions().get("pharId");
		String updUser = page.getConditions().get("updUser");
		StringBuffer sql = new StringBuffer()
		.append("update dic_phar set phar_code = :pharCode,phar_name = :pharName,")
		.append("upd_datetime = sysdate(),upd_user = :updUser where phar_id = :pharId");
		Query query = session.createSQLQuery(sql.toString());
		query.setString("pharCode", pharCode);
		query.setString("pharName", pharName);
		query.setString("pharId", pharId);
		query.setString("updUser", updUser);
		query.executeUpdate();
		session.flush();
		writeLog(pharId);
	}
	
	/**
	 * @category 新增保存
	 * @date 2015年7月13日
	 */
	@Override
	public void addSave(Pagination page){
		Session session = sessionFactory.getCurrentSession();
		String pharCode = page.getConditions().get("pharCode");
		String pharName = page.getConditions().get("pharName");
		String fatherId = page.getConditions().get("fatherId");
		String updUser = page.getConditions().get("updUser");
		String pharId = UUID.randomUUID().toString();
		StringBuffer sql = new StringBuffer()
		.append("	insert into dic_phar select wc.* from (select :pharId,:pharCode pharCode,")
		.append("	CASE WHEN t.phar_id IS NULL THEN (SELECT CASE WHEN s.phar_id IS NULL THEN '1' ELSE CONCAT(s.hierarchy,'.1') END FROM dic_phar s WHERE s.phar_id = :fatherId) ELSE  ")
		.append("	CONCAT(LEFT(MIN(t.hierarchy),CHAR_LENGTH(MIN(t.hierarchy))-1),")
		.append("	MAX(REPLACE(t.hierarchy,")
		.append("	(SELECT LEFT(MIN(hierarchy),CHAR_LENGTH(MIN(hierarchy))-1)")
		.append("	FROM dic_phar  WHERE father_id = :fatherId),'')+0)+1) END tp,")
		.append("	:pharName pharName,:fatherId,1,sysdate(),:updUser,max(sort_id)+1 ")
		.append("	FROM dic_phar t WHERE t.father_id = :fatherId) wc ");
		Query query = session.createSQLQuery(sql.toString());
		query.setString("fatherId", fatherId);
		query.setString("pharCode", pharCode);
		query.setString("pharName", pharName);
		query.setString("pharId", pharId);
		query.setString("updUser", updUser);
		query.executeUpdate();
		session.flush();
		writeLog(pharId);
	}
	
	/**
	 * 根据条件获取不分页数据
	 * @param page
	 * @return page
	 */
	@Override
	public Pagination getDicPharNoPage(Pagination page){
		String pharCode = page.getConditions().get("pharCode");
		String pharName = page.getConditions().get("pharName");
		String status = page.getConditions().get("status");
		StringBuffer sql = new StringBuffer()
		.append("select phar_code pharCode,phar_name pharName,case status when '0' then '停用' else '启用' end status from dic_phar where 1 = 1 ");
		Map<String,Object> params = new HashMap<String, Object>();
		if(StringUtils.isNotBlank(pharCode)){
			sql.append(" and phar_code = :pharCode ");
			params.put("pharCode", pharCode);
		}
		if(StringUtils.isNotBlank(pharName)){
			sql.append(" and phar_name like :pharName ");
			params.put("pharName", "%"+pharName+"%");
		}
		if(StringUtils.isNotBlank(status)){
			sql.append(" and status = :status ");
			params.put("status", "0".equals(status)?"停用":"启用");
		}
		sql.append(" order by phar_code ");
		page.setRows(dao.getSqlMapList(sql.toString(), params));
		return page;
	}
}
